# call()
, apply()
, bind()
的区别
通常,在对象的某个方法 obj.fn()
中使用了 this
,需要改变此 this
的指向时,会使用到call()
, apply()
, bind()
。
obj.fn.call(newThisObj)
obj.fn.apply(newThisObj)
obj.fn.bind(newThisObj)()
1
2
3
4
5
2
3
4
5
obj.fn
方法中的 this
将会指向传入的第一个参数(对象)。
# 详情实例
var uname = 'Bob'
var age = 20
const Man1 = {
uname: 'Tom',
age: 21,
intro () {
console.log(`${this.uname}, ${this.age}`)
},
introMore (like, dislike) {
console.log(`${this.uname}, ${this.age}, like: ${like}, dislike: ${dislike}`)
}
}
const Man2 = {
uname: 'Jerry',
age: 22
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
# 仅改变 this
,不传递额外参数时
Man1.intro() // Tom, 21
// call(), apply(), bind() 不传入参数时,程序默认将 window 对象传入,this 将指向 window
Man1.intro.call() // Bob, 20
Man1.intro.apply() // // Bob, 20
Man1.intro.bind()() // Bob, 20
Man1.intro.call(Man2) // Jerry, 22
Man1.intro.apply(Man2) // Jerry, 22
Man1.intro.bind(Man2)() // Jerry, 22
1
2
3
4
5
6
7
8
9
10
2
3
4
5
6
7
8
9
10
call()
,apply()
,bind()
仅传入一个对象作为第一个参数时,结果一致,仅bind()
使用方式上有区别; 注意:bind()
绑定后返回一个新的函数,不会执行,需要手动调用才会执行。
# 改变 this
,同时还需要传递额外参数时
Man1.introMore('music', 'sports') // Tom, 21, like: music, dislike: sports
Man1.introMore.call(this, 'music', 'sports') // Bob, 20, like: music, dislike: sports
Man1.introMore.apply(this, ['music', 'sports']) // Bob, 20, like: music, dislike: sports
Man1.introMore.bind(this, 'music', 'sports')() // Bob, 20, like: music, dislike: sports
Man1.introMore.call(Man2, 'music', 'sports') // Jerry, 22, like: music, dislike: sports
Man1.introMore.apply(Man2, ['music', 'sports']) // Jerry, 22, like: music, dislike: sports
Man1.introMore.bind(Man2, 'music', 'sports')() // Jerry, 22, like: music, dislike: sports
Man1.introMore.bind(Man2, ['music', 'sports'])() // Jerry, 22, like: music,sports, dislike: undefined
1
2
3
4
5
6
7
8
9
10
11
2
3
4
5
6
7
8
9
10
11
obj.fn
方法中需要传参时,第一个参数必须指定一个对象作为 this 的指向,传递参数从第二个参数开始;call()
,bind()
传递的多个参数以逗号隔开,apply()
传递的参数必须放在数组中作为第二个参数; 注意:bind()
绑定后返回一个新的函数,不会执行,需要手动调用才会执行。
# 总结
call()
, apply()
, bind()
在使用上有区别,在结果上一致,具体使用结合情况使用。
call()
,apply()
: 临时替换this
,并立刻调用一次函数,独立参数用call()
, 数组参数用apply()
;bind()
: 创建并返回新函数,但不会执行,可在需要时再手动调用,此新函数会永久绑定this
。